﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.Windows.Controls;
using System.Windows.Data;
using System.Windows.Documents;
using System.Windows.Input;
using System.Windows.Media;
using System.Windows.Media.Imaging;
using System.Windows.Shapes;
using System.ComponentModel;
using VIBlend.WPF.Controls;
using System.Collections.ObjectModel;

namespace AnonsaiWPF.CSharp.DataGridViewDemos
{
    [Category("VIBlend.WPF.Examples")]
    public partial class AddNewRow : Window, IWindow
    {
        DataTemplate unitPriceColumnDataTemplate;
        DataTemplate totalColumnDataTemplate;
        public AddNewRow()
        {
            InitializeComponent();

            PrepareGridData();

            dataGrid.BindingComplete += new EventHandler(dataGrid_BindingComplete);
            this.unitPriceColumnDataTemplate = this.Resources["unitPriceColumnDataTemplate"] as DataTemplate;
            this.totalColumnDataTemplate = this.Resources["totalColumnDataTemplate"] as DataTemplate;
    
            dataGrid.ItemsSource = listSaleRecord;

            btnAddNewRow.Click += new RoutedEventHandler(btnAddNewRow_Click);
            btnDeleteRow.Click += new RoutedEventHandler(btnDeleteRow_Click);

            // sets the selection mode to full row selection.
            dataGrid.SelectionMode = VIBlend.WPF.Controls.DataGrid.SELECTION_MODE.FULL_ROW_SELECT;

            // disables rows and columns resizing.
            dataGrid.ColumnsHierarchy.AllowResize = false;
            dataGrid.RowsHierarchy.AllowResize = false;

        }

        void dataGrid_BindingComplete(object sender, EventArgs e)
        {
            if (dataGrid.RowsHierarchy.Items.Count == 0)
                return;

            for (int i = 0; i < dataGrid.ColumnsHierarchy.Items.Count; i++)
            {
                dataGrid.ColumnsHierarchy.Items[i].SortMode = GridItemSortMode.Automatic;
                dataGrid.ColumnsHierarchy.Items[i].CellStyle = Application.Current.Resources["TextCenteredCellStyle"] as Style;
            }
         
            dataGrid.ColumnsHierarchy.Items[4].CellDataTemplate = this.unitPriceColumnDataTemplate;
            dataGrid.ColumnsHierarchy.Items[5].CellDataTemplate = this.totalColumnDataTemplate;

            dataGrid.RowsHierarchy.Visible = false;
         
            // manually sets the columns width.
            dataGrid.ColumnsHierarchy.Items[0].Width = 160;
            dataGrid.ColumnsHierarchy.Items[1].Width = 140;
            dataGrid.ColumnsHierarchy.Items[2].Width = 140;
            dataGrid.ColumnsHierarchy.Items[3].Width = 90;
            dataGrid.ColumnsHierarchy.Items[4].Width = 72;
            dataGrid.ColumnsHierarchy.Items[5].Width = 80;

            dataGrid.ColumnsHierarchy.AllowDragDrop = false;
            dataGrid.ColumnsHierarchy.AllowResize = false;

            dataGrid.Refresh();
        }

        void btnAddNewRow_Click(object sender, RoutedEventArgs e)
        {
            dataGrid.RowsHierarchy.ClearSelection();

            // Adds new record.
            listSaleRecord.Add(GenerateNewRecord());
            HierarchyItem lastRowItem = dataGrid.RowsHierarchy.Items[dataGrid.RowsHierarchy.Items.Count - 1];
            dataGrid.EnsureVisible(lastRowItem);
           
            // Selects the new record.
            dataGrid.RowsHierarchy.SelectItem(lastRowItem);
            dataGrid.Refresh();
        }


        protected override void OnClosing(CancelEventArgs e)
        {
            base.OnClosing(e);
            this.listSaleRecord.Clear();
            this.listSaleRecord = null;

            dataGrid.BindingComplete -= new EventHandler(dataGrid_BindingComplete);            
            btnAddNewRow.Click -= new RoutedEventHandler(btnAddNewRow_Click);
            btnDeleteRow.Click -= new RoutedEventHandler(btnDeleteRow_Click);

            this.dataGrid.Dispose();
            this.dataGrid = null;
        }
  

        void btnDeleteRow_Click(object sender, RoutedEventArgs e)
        {
            if (dataGrid.RowsHierarchy.SelectedItems.Length == 1)
            {
                // deletes the selected record.
                int rowToDelete = dataGrid.RowsHierarchy.SelectedItems[0].BoundFieldIndex;
                listSaleRecord.RemoveAt(rowToDelete);
                dataGrid.RowsHierarchy.ClearSelection();
                if (listSaleRecord.Count > rowToDelete)
                {
                    dataGrid.RowsHierarchy.SelectItem(dataGrid.RowsHierarchy.Items[rowToDelete]);
                }
                else if (listSaleRecord.Count > 0)
                {
                    dataGrid.RowsHierarchy.SelectItem(dataGrid.RowsHierarchy.Items[listSaleRecord.Count - 1]);
                }

                dataGrid.Refresh();
            }
        }

        public void SetTheme()
        {
            dataGrid.FontFamily = new FontFamily("Tahoma");
        }
  

        #region Sample Data

        #region Data
        string[] firstNames = new string[] 
                {
                    "Andrew",
                    "Nancy",
                    "Shelley",
                    "Regina",
                    "Yoshi",
                    "Antoni",
                    "Mayumi",
                    "Ian",
                    "Peter",
                    "Lars",
                    "Petra",
                    "Martin",
                    "Sven",
                    "Elio",
                    "Beate",
                    "Cheryl",
                    "Michael",
                    "Guylène"
                };

        string[] lastNames = new string[] 
                {
                    "Fuller",
                    "Davolio",
                    "Burke",
                    "Murphy",
                    "Nagase",
                    "Saavedra",
                    "Ohno",
                    "Devling",
                    "Wilson",
                    "Peterson",
                    "Winkler",
                    "Bein",
                    "Petersen",
                    "Rossi",
                    "Vileid",
                    "Saylor",
                    "Björn",
                    "Nodier"
                };

        static string[,] productNames = new string[,] 
                {
                    {"Black Tea", "1.95"},
                    {"Green Tea", "1.95"},
                    {"Caffè Espresso", "1.45"},
                    {"Doubleshot Espresso", "1.75"},
                    {"Caffè Latte", "2.25"},
                    {"White Chocolate Mocha", "2.35"},
                    {"Caramel Latte", "2.35"},
                    {"Caffè Americano", "1.65"},
                    {"Cappuccino", "2.10"},
                    {"Espresso Truffle", "2.45"},
                    {"Espresso con Panna", "1.81"},
                    {"Peppermint Mocha Twist", "1.99"}
                };

        public class EmployeeSaleRecord
        {
            public EmployeeSaleRecord(string Name, DateTime Date, int ProductId, int Quantity)
            {
                this._name = Name;
                this._date = Date;
                this._productid = ProductId;
                this._quantity = Quantity;
            }

            #region Private Members
            private string _name;
            private DateTime _date;
            private int _productid;
            private int _quantity;
            #endregion

            #region Properties

            public string Name
            {
                get { return _name; }
                set { _name = value; }
            }

            public DateTime Date
            {
                get { return _date; }
                set { _date = value; }
            }

            public string Product
            {
                get { return productNames[_productid, 0]; }
            }

            public int Quantity
            {
                get { return _quantity; }
                set { _quantity = value; }
            }

            public double UnitPrice
            {
                get
                {
                    double unitPrice = double.Parse(productNames[_productid, 1]);
                    return unitPrice;
                }
            }

            public double SalesAmount
            {
                get { return (double)_quantity * UnitPrice; }
            }


            #endregion
        }


        #endregion

        public ObservableCollection<EmployeeSaleRecord> listSaleRecord = new ObservableCollection<EmployeeSaleRecord>();

        Random rand = new Random();

        private void PrepareGridData()
        {
            const int rowsToLoad = 15;
            listSaleRecord.Clear();
            for (int i = 0; i < rowsToLoad; i++)
            {
                listSaleRecord.Add(GenerateNewRecord());
            }
        }

        private EmployeeSaleRecord GenerateNewRecord()
        {
            int productId = rand.Next(0, productNames.Length / 2 - 1);
            int quantity = rand.Next(1, 5);

            EmployeeSaleRecord record = new EmployeeSaleRecord(
                string.Format("{0} {1}",
                firstNames[rand.Next(0, firstNames.Length - 1)],
                lastNames[rand.Next(0, lastNames.Length - 1)]),
                DateTime.Now.AddDays(-rand.Next(10, 100)),
                productId,
                quantity);

            return record;
        }

        #endregion

        // Custom class implements the IValueConverter interface.
        public class ProductIdToNameConverter : IValueConverter
        {
            #region IValueConverter Members

            public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
            {
                if ((int)value >= productNames.Length / 2)
                    return "";

                return productNames[(int)value, 0];
            }

            public object ConvertBack(object value, Type targetType,
                object parameter, System.Globalization.CultureInfo culture)
            {
                throw new NotImplementedException();
            }

            #endregion
        }


        #region IWindow Members

        public void DetachContent()
        {
            RemoveLogicalChild(Content);
        }

        #endregion

        #region IWindow Members


        public Grid Root
        {
            get
            {
                return this.LayoutRoot;
            }
        }

        #endregion
    } // class CellEditing

    public class ProductIdToNameConverter : IValueConverter
    {
        static string[,] productNames = new string[,] 
                {
                    {"Black Tea", "1.95"},
                    {"Green Tea", "1.95"},
                    {"Caffè Espresso", "1.45"},
                    {"Doubleshot Espresso", "1.75"},
                    {"Caffè Latte", "2.25"},
                    {"White Chocolate Mocha", "2.35"},
                    {"Caramel Latte", "2.35"},
                    {"Caffè Americano", "1.65"},
                    {"Cappuccino", "2.10"},
                    {"Espresso Truffle", "2.45"},
                    {"Espresso con Panna", "1.81"},
                    {"Peppermint Mocha Twist", "1.99"}
                };

        #region IValueConverter Members

        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            if ((int)value >= productNames.Length / 2)
                return "";

            return productNames[(int)value, 0];
        }

        public object ConvertBack(object value, Type targetType,
            object parameter, System.Globalization.CultureInfo culture)
        {
            throw new NotImplementedException();
        }

        #endregion
    }

    public class ShortDateConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            return string.Format("{0:MMMM, yyyy}", (DateTime)value);
        }

        public object ConvertBack(object value, Type targetType,
            object parameter, System.Globalization.CultureInfo culture)
        {
            return DateTime.Parse(value.ToString());
        }
    }

    public class DateConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            return string.Format("{0:dd-MMM-yyyy}", (DateTime)value);
        }

        public object ConvertBack(object value, Type targetType,
            object parameter, System.Globalization.CultureInfo culture)
        {
            return DateTime.Parse(value.ToString());
        }
    }

    public class CurrencyConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            double dblVal = 0.0;
            if (value != null)
            {
                double.TryParse(value.ToString(), out dblVal);
            }
            else
            {
                return string.Empty;
            }

            return string.Format("{0:C}", dblVal);
        }

        public object ConvertBack(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            return double.Parse(value.ToString(), System.Globalization.NumberStyles.Currency);
        }
    }

    public class DateTimeConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            return string.Format("{0:d}", (DateTime)value);
        }

        public object ConvertBack(object value, Type targetType,
            object parameter, System.Globalization.CultureInfo culture)
        {
            if (value != null)
            {
                return DateTime.Parse(value.ToString());
            }
            else
            {
                return DateTime.Now.Date;
            }
        }
    }

    public class TimeConverter : IValueConverter
    {
        public object Convert(object value, Type targetType, object parameter, System.Globalization.CultureInfo culture)
        {
            return string.Format("{0:d}", (DateTime)value);
        }

        public object ConvertBack(object value, Type targetType,
            object parameter, System.Globalization.CultureInfo culture)
        {
            if (value != null)
            {
                return DateTime.Parse(value.ToString());
            }
            else
            {
                return DateTime.Now.Date;
            }
        }
    }
}
